﻿using Myotragus.Data.Emit;
using NHibernate;
using NHibernate.Criterion;
using NHibernate.SqlCommand;

namespace Myotragus.Data.Criteria
{
	public class DefaultsLocalizableAlias : LocalizableAlias, IDefaultsLocalizableAlias
	{
		public override ICriteria CreateAlias(ICriteria criteria, string path, string alias,
			JoinType joinType, int lcId)
		{
			// select (case when <alias>.Value is not null <alias>.Value else ) as <alias> from <table>
			//	left outer join
			//	<TextValues> <alias> on <table>.<alias>=<TextValues>.TextId and
			//		<alias>.LcId=?p0_LcId
			//	inner join
			//	<Text> CreateAlias(Text) on <table>.<alias>=CreateAlias(Text).TextId
			//		left outer join
			//		<TextValues> CreateDefaults<join> on Text<join>.TextId=Default<join>.TextId and
			//			Text<join>.DefaultLcId=Default<join>.LcId

			//	<joinType> <path>.<alias> as <alias> on <alias>.LcId=:lcId
			var prefix = string.IsNullOrEmpty(path) ? "" : string.Concat(path, ".");

			var lcRestriction = Restrictions.Eq(string.Format("{0}.LcId", alias), lcId);
			criteria.CreateAlias(string.Concat(prefix, alias), alias, joinType, lcRestriction);

			//	inner join <path>.<CreateDefaultName(alias)> as CreateDefaultName(alias)
			var defaultPropertyName = EmitHelper.CreateDefaultsName(alias);
			criteria.CreateAlias(string.Concat(prefix, defaultPropertyName), defaultPropertyName,
				JoinType.InnerJoin);

			//	left outter join <CreateDefaultName(alias)>.Values as <CreateAlias("DefaultValues", alias)>
			var propertyDefaultValues = EmitHelper.CreateAlias("DefaultValues", alias);
			var defaultLcRestriction = Restrictions.EqProperty(
				string.Concat(defaultPropertyName, ".DefaultLcId"),
				string.Concat(propertyDefaultValues, ".LcId")
				);
			criteria.CreateAlias(string.Concat(defaultPropertyName, ".Values"), propertyDefaultValues,
				JoinType.LeftOuterJoin, defaultLcRestriction);

			return criteria;
		}
	}
}